#include "gameroom.h"
#include "gameselect.h"
#include <QPainter>
#include <QIcon>
#include <QTimer>
#include <QPushButton>
#include <QMessageBox>
#include <QFile>
#include <QTextStream>

GameRoom::GameRoom(QWidget *parent) : QWidget(parent)
{
    this->setWindowIcon(QIcon(":/res/icon.jpg"));
    this->setFixedSize(1000, 900);
    this->setWindowTitle("游戏房间");

    //初始化贪吃蛇
    snakeList.push_back(QRectF(400, 200, snakeNodeWidth, snakeNodeHeight));
    moveUp();
    moveUp();

    //创建食物
    createNewFood();

    //创建定时器
    timer = new QTimer(this);
    connect(timer, &QTimer::timeout, [=](){
        int cnt = 1;
        if (snakeList.front().intersects(foodRect)) // 判断蛇头是否吃掉食物
        {
            createNewFood();
            cnt++;
        }
        while(cnt--)
        {
            switch (moveDirect)
            {
                case SnakeDirect::UP:
                    moveUp();
                    break;
                case SnakeDirect::DOWN:
                    moveDown();
                    break;
                case SnakeDirect::LEFT:
                    moveLeft();
                    break;
                case SnakeDirect::RIGHT:
                    moveRight();
                    break;
            }
        }
        snakeList.pop_back();
        update();
    });

    //开始与暂停
    QPushButton* startButton = new QPushButton(this);
    QPushButton* stopButton = new QPushButton(this);
    QFont font_1("楷体", 20);
    startButton->setFont(font_1);
    stopButton->setFont(font_1);
    startButton->move(860, 100);
    stopButton->move(860, 200);
    startButton->setText("开始");
    stopButton->setText("暂停");
    QString style_1("QPushButton{border : 5px solid #ee0000; border-radius : 10px; color : #33ffcc;} "
                         "QPushButton:hover{border : 5px solid #33ffcc; color : #ee0000;}");
    startButton->setStyleSheet(style_1);
    stopButton->setStyleSheet(style_1);

    connect(startButton, &QPushButton::clicked, [=](){
        if (isGameStart == true)
        {
            return;
        }
        isGameStart = true;
        timer->start(moveTimeout);
        sound = new QSound(":/res/game_room.wav");
        sound->play();
        sound->setLoops(-1);
    });
    connect(stopButton, &QPushButton::clicked, [=](){
        if (isGameStart == false)
        {
            return;
        }
        isGameStart = false;
        timer->stop();
        sound->stop();
    });

    //方向控制
    QPushButton* up = new QPushButton(this);
    QPushButton* down = new QPushButton(this);
    QPushButton* left = new QPushButton(this);
    QPushButton* right = new QPushButton(this);

    up->setText("↑");
    down->setText("↓");
    left->setText("←");
    right->setText("→");

    QFont font_2("宋体", 20);
    up->setFont(font_2);
    down->setFont(font_2);
    left->setFont(font_2);
    right->setFont(font_2);

    up->move(880, 300);
    down->move(880, 400);
    left->move(820, 350);
    right->move(940, 350);

    up->setShortcut(QKeySequence(Qt::Key_Up));
    down->setShortcut(QKeySequence(Qt::Key_Down));
    left->setShortcut(QKeySequence(Qt::Key_Left));
    right->setShortcut(QKeySequence(Qt::Key_Right));

    QString style_2("QPushButton{border : 5px solid #ee0000; border-radius : 20px; color : #33ffcc;} "
                    "QPushButton:hover{border : 5px solid #33ffcc; color : #ee0000;}");
    up->setStyleSheet(style_2);
    down->setStyleSheet(style_2);
    left->setStyleSheet(style_2);
    right->setStyleSheet(style_2);

    connect(up, &QPushButton::pressed, [=](){
        if (moveDirect != SnakeDirect::DOWN && moveDirect != SnakeDirect::UP)
        {
            moveDirect = SnakeDirect::UP;
        }
    });
    connect(down, &QPushButton::pressed, [=](){
        if (moveDirect != SnakeDirect::DOWN && moveDirect != SnakeDirect::UP)
        {
            moveDirect = SnakeDirect::DOWN;
        }
    });
    connect(left, &QPushButton::pressed, [=](){
        if (moveDirect != SnakeDirect::LEFT && moveDirect != SnakeDirect::RIGHT)
        {
            moveDirect = SnakeDirect::LEFT;
        }
    });
    connect(right, &QPushButton::pressed, [=](){
        if (moveDirect != SnakeDirect::RIGHT && moveDirect != SnakeDirect::LEFT)
        {
            moveDirect = SnakeDirect::RIGHT;
        }
    });

    // 返回按钮
    QPushButton* backButton = new QPushButton(this);
    backButton->move(830, 500);
    backButton->setStyleSheet("QPushButton{border : 0px; width : 150px; height : 100px; image : url(:/res/back.png);}"
                              "QPushButton:hover{image : url(:/res/back_2.png);}");
    QMessageBox* messageBox = new QMessageBox(this);
    messageBox->setWindowTitle("返回");
    messageBox->setText("确认返回选择菜单吗？");
    QPushButton* accept = new QPushButton("accept");
    QPushButton* cancel = new QPushButton("cancel");
    messageBox->addButton(accept, QMessageBox::AcceptRole);
    messageBox->addButton(cancel, QMessageBox::RejectRole);

    connect(backButton, &QPushButton::clicked, [=](){
        stopButton->clicked();
        messageBox->show();
        messageBox->exec();//事件轮询
        if(messageBox->clickedButton() == accept)
        {
            this->close();
            GameSelect* gameselect = new GameSelect;
            gameselect->show();
        }
        else
        {
            messageBox->close();
            startButton->clicked();
        }
    });
    connect(backButton, &QPushButton::pressed, [=](){
        QSound::play(":/res/start.wav");
    });
}

void GameRoom::paintEvent(QPaintEvent *event)
{
    //绘制大厅背景
    (void)event;
    QPainter painter(this);
    QPixmap pixmap;
    pixmap.load(":/res/game_room_1.png");
    painter.drawPixmap(0, 0, 800, 900, pixmap);
    pixmap.load(":/res/game_room_2.jpg");
    painter.drawPixmap(800, 0, 200, 900, pixmap);

    //绘制蛇: 蛇头 + 蛇身体 + 蛇尾巴
    //绘制蛇头: 上 下 左 右
    if (moveDirect == SnakeDirect::UP)
    {
        pixmap.load(":/res/up.png");
    }
    else if(moveDirect == SnakeDirect::DOWN)
    {
        pixmap.load(":/res/down.png");
    }
    else if(moveDirect == SnakeDirect::LEFT)
    {
        pixmap.load(":/res/left.png");
    }
    else if(moveDirect == SnakeDirect::RIGHT)
    {
        pixmap.load(":/res/right.png");
    }
    QRectF snakeHead = snakeList.front();
    painter.drawPixmap(snakeHead.x(), snakeHead.y(), snakeHead.width(), snakeHead.height(), pixmap);

    //绘制蛇身
    pixmap.load(":/res/body.png");
    for (int i = 1; i < snakeList.size() - 1; i++)
    {
        QRectF snakeBody = snakeList[i];
        painter.drawPixmap(snakeBody.x(), snakeBody.y(), snakeBody.width(), snakeBody.height(), pixmap);
    }

    //绘制蛇的尾巴
    pixmap.load(":/res/tail.png");
    QRectF snakeTail = snakeList.back();
    painter.drawPixmap(snakeTail.x(), snakeTail.y(), snakeTail.width(), snakeTail.height(), pixmap);

    //绘制食物
    pixmap.load(":/res/food.png");
    painter.drawPixmap(foodRect.x(), foodRect.y(), foodRect.width(), foodRect.height(), pixmap);

    //绘制分数
    pixmap.load(":/res/");
    painter.drawPixmap(850, 700, 100, 50, pixmap);

    QPen pen;
    pen.setColor(Qt::black);
    painter.setPen(pen);
    painter.setFont(QFont("微软雅黑", 30));
    painter.drawText(890, 700, QString("%1").arg(snakeList.size() - 3));

    //绘制游戏失败效果
    if (checkFail())
    {
        pen.setColor(Qt::red);
        painter.setPen(pen);
        painter.setFont(QFont("微软雅黑", 50));
        painter.drawText(this->width() * 0.20, this->height() * 0.5, QString("GAME OVER"));
        timer->stop();
        sound->stop();
        //emit gameover();
    }

    //向文件中写分数
    int score = snakeList.size() - 3;
    QFile file("C:/Users/wangd/Desktop/greedy_snake/Snake/res/topScore.txt");
    file.open(QIODevice::ReadOnly| QIODevice::Text);
    QTextStream in(&file);
    int num = in.readLine().toInt();
    file.close();
    if (score > num)
    {
        file.open(QIODevice::WriteOnly | QIODevice::Text | QIODevice::Truncate);
        QTextStream out(&file);
        out << score;
        file.close();
    }
}

void GameRoom::moveUp()
{
    QPointF topLeft; //左上角坐标
    QPointF buttomRight; //右下角坐标

    QRectF snakeNode = snakeList.front(); //获取到头
    int headX = snakeNode.x();
    int headY = snakeNode.y();

    if(headY <= 0) //穿墙了
    {
        topLeft = QPointF(headX, this->height() - snakeNodeHeight);
    }
    else
    {
        topLeft = QPointF(headX, headY - snakeNodeHeight);
    }
    buttomRight = topLeft + QPointF(snakeNodeWidth, snakeNodeHeight);
    snakeList.push_front(QRectF(topLeft, buttomRight));
}

void GameRoom::moveDown()
{
    QPointF topLeft; //左上角坐标
    QPointF buttomRight; //右下角坐标

    QRectF snakeNode = snakeList.front(); //获取到头
    int headX = snakeNode.x();
    int headY = snakeNode.y();

    if (headY + snakeNodeHeight >= this->width()) //穿墙
    {
        topLeft = QPointF(headX, 0);
    }
    else
    {
        topLeft = QPointF(headX, headY + snakeNodeHeight);
    }
    buttomRight = topLeft + QPointF(snakeNodeWidth, snakeNodeHeight);
    snakeList.push_front(QRectF(topLeft, buttomRight));
}

void GameRoom::moveLeft()
{
    QPointF topLeft; //左上角坐标
    QPointF buttomRight; //右下角坐标

    QRectF snakeNode = snakeList.front();
    int headX = snakeNode.x();
    int headY = snakeNode.y();

    if (headX < 0)
    {
        topLeft = QPointF(800 - snakeNodeWidth, headY);
    }
    else
    {
        topLeft = QPointF(headX - snakeNodeWidth, headY);
    }
    buttomRight = topLeft + QPointF(snakeNodeWidth, snakeNodeHeight);
    snakeList.push_front(QRectF(topLeft, buttomRight));

}

void GameRoom::moveRight()
{
    QPointF topLeft; //左上角坐标
    QPointF buttomRight; //右下角坐标

    QRectF snakeNode = snakeList.front();
    int headX = snakeNode.x();
    int headY = snakeNode.y();

    if (headX + snakeNodeWidth >= 800)
    {
        topLeft = QPointF(0, headY);
    }
    else
    {
        topLeft = QPointF(headX + snakeNodeWidth, headY);
    }
    buttomRight = topLeft + QPointF(snakeNodeWidth, snakeNodeHeight);
    snakeList.push_front(QRectF(topLeft, buttomRight));
}

bool GameRoom::checkFail()
{
    for(int i = 0; i < snakeList.size(); i++)
    {
        for(int j = i + 1; j < snakeList.size(); j++)
        {
            if(snakeList[i] == snakeList[j])
            {
                return true;
            }
        }
    }
    return false;
}

void GameRoom::createNewFood()
{
    foodRect = QRectF(qrand() % (800 / snakeNodeWidth) * snakeNodeWidth, qrand() % (this->height()/snakeNodeWidth) * snakeNodeHeight, snakeNodeWidth, snakeNodeHeight);
    for(int i = 0; i < snakeList.size(); i++)
    {
        if (snakeList[i] == foodRect)
        {
            createNewFood();
        }
        else
        {
            return;
        }
    }
}





